﻿///<copyright>
/// Copyright © 2009 Stephen Styrchak. All Rights Reserved.
///</copyright>
using System;
using System.Collections.Generic;
using System.ComponentModel;
using Microsoft.Xna.Framework;

namespace Ferpect.ComponentModel.Sprites
{
    public enum RotationDirection
    {
        None = 0,
        Clockwise = 1,
        AntiClockwise = -1,
    }

    [ProvideProperty("RotationDirection", typeof(Sprite))]
    [ProvideProperty("RotationsPerSecond", typeof(Sprite))]
    public class SpriteRotation : SpriteAnimation
    {
        private struct RotationInfo
        {
            public float Direction;
            public float RotationsPerSecond;
        }

        private Dictionary<string, RotationInfo> rotationInfo;

        public SpriteRotation()
        {
            this.rotationInfo = new Dictionary<string, RotationInfo>();
        }

        #region IUpdateable Members

        public override void Update(GameTime gameTime)
        {
            float elapsedMilliseconds = (float)gameTime.ElapsedGameTime.TotalMilliseconds;
            foreach (Sprite sprite in this.Sprites)
            {
                float currentRotation = sprite.Rotation;
                RotationInfo parameters = this.rotationInfo[sprite.Name];

                float delta = elapsedMilliseconds * parameters.Direction * parameters.RotationsPerSecond * MathHelper.Pi * 2f / 1000f;
                sprite.Rotation += delta;
            }
        }

        #endregion

        [DefaultValue(RotationDirection.None)]
        [Category("Animation - Rotation")]
        public RotationDirection GetRotationDirection(Sprite sprite)
        {
            RotationInfo info = new RotationInfo();
            this.rotationInfo.TryGetValue(sprite.Name, out info);
            if (info.Direction < 0)
            {
                return RotationDirection.AntiClockwise;
            }
            if (info.Direction > 0)
            {
                return RotationDirection.Clockwise;
            }
            return RotationDirection.None;
        }

        [DefaultValue(RotationDirection.None)]
        [Category("Animation - Rotation")]
        public void SetRotationDirection(Sprite sprite, RotationDirection value)
        {
            RotationInfo info = new RotationInfo();
            if (!this.rotationInfo.TryGetValue(sprite.Name, out info))
            {
                this.Sprites.Add(sprite);
            }
            info.Direction = (float)value;
            this.rotationInfo[sprite.Name] = info;
        }

        [DefaultValue(0f)]
        [Category("Animation - Rotation")]
        public float GetRotationsPerSecond(Sprite sprite)
        {
            RotationInfo info = new RotationInfo();
            this.rotationInfo.TryGetValue(sprite.Name, out info);
            return info.RotationsPerSecond;
        }

        [DefaultValue(0f)]
        [Category("Animation - Rotation")]
        public void SetRotationsPerSecond(Sprite sprite, float value)
        {
            RotationInfo info = new RotationInfo();
            if (!this.rotationInfo.TryGetValue(sprite.Name, out info))
            {
                this.Sprites.Add(sprite);
            }
            info.RotationsPerSecond = value;
            this.rotationInfo[sprite.Name] = info;
        }
    }
}
